/**
 * 
 */
package hu.gbalage.owlforms.xforms;

import java.net.URI;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import hu.gbalage.owlforms.api.Entity;
import hu.gbalage.owlforms.api.Field;
import hu.gbalage.owlforms.api.Form;
import hu.gbalage.owlforms.api.style.FieldTitleProvider;
import hu.gbalage.owlforms.api.style.OWLFormsStyle;

import org.w3c.dom.Document;
import org.w3c.dom.Element;

/**
 * @author Grill Balazs (balage.g@gmail.com)
 *
 */
@Deprecated
public class XFormsGen {

	public static final String NS_XHTML = "http://www.w3.org/1999/xhtml";
	public static final String NS_EVENT = "http://www.w3.org/2001/xml-events";
	public static final String NS_XFORMS = "http://www.w3.org/2002/xforms";
	
	public static final String NS_RDF = "http://www.w3.org/1999/02/22-rdf-syntax-ns";
	public static final String NS_RDFS = "http://www.w3.org/2000/01/rdf-schema";
	public static final String NS_OWL = "http://www.w3.org/2002/07/owl";
	public static final String NS_XSD = "http://www.w3.org/2001/XMLSchema";
	
	public Element createEntityNode(Document doc, Entity entity){
		URI uri = entity.getURI();
		String ns = uri.getScheme()+":/"+uri.getPath();
		//URI nsuri = URI.create(ns);
		String prefix = getPrefix(ns);
		String item = uri.getFragment();
		return doc.createElementNS(ns, prefix+":"+item);
	}
	
	public Document generateModel(Form form){
		Document doc = XMLHelper.createEmptyDoc();
		
		Element e = createEntityNode(doc, form);
		doc.appendChild(e);
		
		for(Field f : form.listFields()){
			Element fe = createEntityNode(doc, f);
			e.appendChild(fe);
		}
		
		return doc;
	}
	
	private OWLFormsStyle style; 
	
	private Element br(Document doc){
		return doc.createElement("xhtml:br");
	}
	
	private void processForm(Document doc, Element modelplace, Element viewplace, Form form){
		Element formmodel = createEntityNode(doc, form);
		modelplace.appendChild(formmodel);
		
		Element group = doc.createElement("xf:group");
		//String refns = getPrefix(formmodel.getNamespaceURI());
		group.setAttribute("ref", /*refns+":"+*/formmodel.getTagName());
		viewplace.appendChild(group);
		
		List<Field> fields = style.getFieldOrderProvider().orderFields(form.listFields());
		FieldTitleProvider title = style.getFieldTitleProvider();
		for(Field field : fields){
			Element ref = createEntityNode(doc, field);
			formmodel.appendChild(ref);
			if (field.isComplex()){
				Form contained = field.asComplexField().getContainedForm()[0]; //: polymorphism
				Element div = doc.createElement("xhtml:div");
				group.appendChild(div);
				processForm(doc, ref, div, contained);
			}else{
				Element input = doc.createElement("xf:input");
				//String ns = getPrefix(ref.getNamespaceURI());
				input.setAttribute("ref", /*ns+":"+*/ref.getTagName());
				group.appendChild(input);
				Element label = doc.createElement("xf:label");
				label.setTextContent(title.getTitle(field));
				input.appendChild(label);
				group.appendChild(br(doc));
			}
		}
	}
	
	private void generateSubmit(Document doc, Element model, Element body){
		Element submission = doc.createElement("xf:submission");
		submission.setAttribute("id","io");
		submission.setAttribute("method","post");
		submission.setAttribute("action", "/io");
		model.appendChild(submission);
		
		Element submit = doc.createElement("xf:submit");
		submit.setAttribute("submission", "io");
		body.appendChild(submit);
		
		Element label = doc.createElement("xf:label");
		label.setTextContent("Elküld");
		submit.appendChild(label);
	}
	
	private Map<String, String> prefixes = new HashMap<String, String>();
	private Element root;
	private String getPrefix(String uri){
		if (!prefixes.containsKey(uri)){
			String ns = "ns"+prefixes.size();
			root.setAttribute("xmlns:"+ns, uri);
			prefixes.put(uri, ns);
		}
		return prefixes.get(uri);
	}
	
	public Document generateXForms(Form form){
		style = form.getStyle();
		
		Document doc = XMLHelper.createEmptyDoc();
		
		Element html = doc.createElementNS(NS_XHTML, "html");
		html.setAttribute("xmlns", NS_XHTML);
		html.setAttribute("xmlns:xhtml", NS_XHTML);
		html.setAttribute("xmlns:rdf", NS_RDF);
		html.setAttribute("xmlns:xf", NS_XFORMS);
		html.setAttribute("xmlns:e", NS_EVENT);
		html.setAttribute("xmlns:rdfs", NS_RDFS);
		html.setAttribute("xmlns:owl", NS_OWL);
		html.setAttribute("xmlns:xsd", NS_XSD);
		root = html;
		doc.appendChild(html);
		
		Element head = doc.createElement("xhtml:head");
		html.appendChild(head);
		
		Element body = doc.createElement("xhtml:body");
		html.appendChild(body);
		
		Element model = doc.createElement("xf:model");
		model.setAttribute("id", "default");
		head.appendChild(model);
		
		Element instance = doc.createElement("xf:instance");
		//instance.setAttribute("xmlns", NS_RDF);
		model.appendChild(instance);
		Element RDF = doc.createElement("rdf:RDF");
		instance.appendChild(RDF);
		
		Element group = doc.createElement("xf:group");
		group.setAttribute("ref","rdf:RDF");
		body.appendChild(group);
		
		processForm(doc,RDF, group, form);
		
		generateSubmit(doc, model, body);
		
		return doc;
	}
	
}
